package com.w.picture.config;

import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.context.event.ApplicationReadyEvent;
import org.springframework.boot.web.server.WebServer;
import org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.event.EventListener;

import java.net.InetAddress;
import java.net.UnknownHostException;

/**
 * Swagger 启动时打印访问地址
 *
 * @author wzp
 * @since 2024/12/14
 */
@Slf4j
@Configuration
public class SwaggerPrintConfig2 {

    /**
     * @EventListener 注解
     * 声明式编程: 使用@EventListener是一种更声明式的编程方式。你只需要在方法上添加这个注解，并指定要监听的事件类型。
     * 简洁性: 它使代码更加简洁，因为你不需要创建一个类来实现某个接口。
     * 灵活性: 你可以监听多个不同类型的事件，甚至可以监听所有事件（通过使用泛型）。此外，还可以指定条件表达式来进一步过滤事件。
     * 自动注册: Spring会自动检测带有@EventListener注解的方法并注册为事件监听器，无需显式配置。
     * <p>
     * ApplicationReadyEvent:
     * 触发时间: 在所有的Spring Bean都已加载并且应用程序已经准备好处理请求时触发。
     * 适用场景: 这是确保应用程序完全启动并可以安全地处理请求的最佳时机。如果你需要确保所有组件都已经正确初始化后再执行某些操作，那么应该选择这个事件。
     * 优点: 应用程序的所有组件和服务都已经准备好，可以安全地进行业务逻辑处理。
     * 缺点: 相较于WebServerInitializedEvent，它会在稍后一点触发。
     */
    @EventListener(ApplicationReadyEvent.class)
    public void printAccessUrls(ApplicationReadyEvent event) {
        // (ServletWebServerApplicationContext) event.getApplicationContext(); 在启动测试类报异常,暂时注释
//        try {
//            // 获取IP地址
//            InetAddress inetAddress = InetAddress.getLocalHost();
//            String hostAddress = inetAddress.getHostAddress();
//
//            // 从ApplicationReadyEvent中获取ApplicationContext
//            ServletWebServerApplicationContext context =
//                    (ServletWebServerApplicationContext) event.getApplicationContext();
//            WebServer webServer = context.getWebServer();
//
//            if (webServer != null) {
//                int port = webServer.getPort();
//
//                // 打印启动信息和Swagger UI地址
//                log.info("项目启动成功！访问地址: http://{}:{}", "127.0.0.1", port);
//                log.info("Knife4j UI: http://{}:{}/doc.html", "127.0.0.1", port);
//            } else {
//                log.warn("web服务器不可用。");
//            }
//
//        } catch (UnknownHostException e) {
//            log.error("无法获取主机地址", e);
//        }
    }
}
